# 引用: 其实就是变量和数据之间的关联关系
# 例如: a = 1  此时我们将数据1 赋值给了变量a 则a 就引用了1
# 如果引用关系切断,此时a 会消失,1也不存在了

# 怎样判断引用关系: 赋值  容器
# a = 1 此时  a 引用了1
# list1 = [1,2,3,4]  list1 引用了[1,2,3,4]这个列表, list1[0]引用了1 这个数据
# 在Python中所有的数据存储都是引用关系

# 引用地址 : 其实python中的引用地址,就是根据内存地址计算出来的唯一标识,我们可以认为引用地址就是内存地址,引用地址相同数据一定相同
# 使用is关键字,可以判断数据的引用地址是否相同, 使用id 可以输出变量的引用地址
print('----------------使用is关键字,可以判断数据的引用地址是否相同, 使用id 可以输出变量的引用地址------------------')
# 1. 数据的类型相同一定是同一个数据么?  不一定
print('1' is '2')  # False
print(id('1'))  # 2090987168880
print(id('2'))  # 2090988554480

print('-----------------数据的值相同一定是同一个数据么?  不一定-----------------')
# 2. 数据的值相同一定是同一个数据么?  不一定
print(True == 1)  # True 值相同
print(True is 1)  # False 不是同一个数据
print(id(True))  # 140709490235216
print(id(1))  # 140709490513568

print('-------数据的值和类型都相同一定是同一个数据么? 不一定------')

# 3. 数据的值和类型都相同一定是同一个数据么? 不一定
list1 = [1, 2, 3]
list2 = [1, 2, 3]

print(list1 == list2)  # True 数据的值相同
print(list1 is list2)  # False 不是同一个数据, 内存地址不相同

print('------1-------')

tuple1 = (1, 2, 3)
tuple2 = (1, 2, 3)

print(tuple1 == tuple2)  # True
print(tuple1 is tuple2)  # True

print('-------2------')

set1 = {1, 2, 3}
set2 = {1, 2, 3}

print(set1 == set2)  # True
print(set1 is set2)  # False

print('------3-------')

str1 = '123'
str2 = '123'

print(str1 == str2)  # True
print(str1 is str2)  # True

print('------4-------')

dict1 = {'a': 1}
dict2 = {'a': 1}

print(dict1 == dict2)  # True
print(dict1 is dict2)  # False


# 因为内部数据可以修改的数据类型,如果数据的值相同,数据就存储在一个内存空间中,则修改一个,另一个也修改了
print('-----------------因为内部数据可以修改的数据类型,如果数据的值相同,数据就存储在一个内存空间中,则修改一个,另一个也修改了-----------------')
list1 = [1, 2, 3]
list2 = list1
# 此时 list1, 和list2 引用地址相同
print(id(list1))  # 2791737937600
print(id(list2))  # 2791737937600

print('----------------------------------')
# 给list1内部增加一个数值
list1.append(4)
# 此时内存地址相同,修改一个其他的也发生变化
print(list1) # [1, 2, 3, 4]
print(list2) # [1, 2, 3, 4]


# 结论:
# 1. 使用id 可以查看引用地址, 使用is 可以判断两个数据的引用地址是否相同,引用地址相同则一定是同一个数据
# 2. 经过观察发现 容器类型中 列表 集合 字典 数据值相同 类型也相同,不一定引用地址相同,也就不一定是同一个数据
# 3. 字符串, 元组 数据值相同, 类型也相同, 引用地址就相同也就是是同一个数据
# 4. 如果两个变量引用的是同一个内存空间中的数据,则修改内存空间中的数据,两个变量同时改变

